#include "cTools.h"


extern ID3DXFont* pFont;
extern cTools *pTools;

VOID cTools::DrawTxt(INT X, INT Y, D3DCOLOR Color, ID3DXFont *font, CONST PCHAR Text, DWORD flag ) 
{		
	if( !Text || *Text == '\0' )
		return;

	RECT Pos = { X, Y, X+500, Y+50 };
	font->DrawTextA( NULL, Text, -1, &Pos, flag/* | DT_NOCLIP*/, Color);
}
//-----------------------//
// cTools::MemPatch
//-----------------------//
VOID cTools::MemPatch(PUCHAR dest, CONST PUCHAR src, INT len)
{
	DWORD dwOld;
	VirtualProtect(dest, len, PAGE_READWRITE, &dwOld);
	for(int i = 0; i < len; i++)
	{
		dest[i] = src[i];
	}
	VirtualProtect(dest, len, dwOld, &dwOld);
	FlushInstructionCache(0, dest, len);
}
//-----------------------//
// cTools::MemPatch
//-----------------------//
VOID cTools::MemSet(PBYTE dest, INT val, INT len)
{
	DWORD dwOld;
	VirtualProtect(dest, len, PAGE_READWRITE, &dwOld);
	for(int i = 0; i < len; i++)
	{
		dest[i] = val;
	}
	VirtualProtect(dest, len, dwOld, &dwOld);
}
//-----------------------//
// cTools::DirectMemAlloc
//-----------------------//
VOID cTools::DirectMemAlloc(PUCHAR dest, INT len)
{
	DirectMemAllocMemPtr = new (dest) unsigned char[len];
}

//-----------------------//
// cTools::MemXorJmp
//-----------------------//
VOID cTools::MemXorJmp(DWORD xorcave, DWORD jumpto)// written by Hans211
{
	struct {
		BYTE    op1;               // mov eax, adr
		DWORD   adr;
		BYTE    op2;               // xor eax, mask
		DWORD   mask;
		BYTE    jmp;               // jmp eax
		BYTE    eax;
	} MASQ = { 0xb8,0,0x35,0x55,0xff,0xe0};

	MASQ.adr = jumpto^MASQ.mask;
	DWORD dwOld;
	VirtualProtect((void*)xorcave, 12, PAGE_READWRITE, &dwOld);
	memset((BYTE*)xorcave, MASQ.op1, 1); //2 (const unsigned char *)
	*(DWORD*)(xorcave + 1) = MASQ.adr;
	memset((BYTE*)xorcave + 5, MASQ.op2, 1);
	memset((BYTE*)xorcave + 6, MASQ.mask, 1);
	memset((BYTE*)xorcave + 10, MASQ.jmp, 1);
	memset((BYTE*)xorcave + 11, MASQ.eax, 1);
	VirtualProtect((void*)xorcave, 12, dwOld, &dwOld);
}

//-----------------------//
// cTools::MemHotPatch
//-----------------------//
DWORD cTools::MemHotPatch(DWORD adr, DWORD caveadr, bool dip_special) // written by Hans211, edited by N1ghtmare
{
	if(!dip_special){
		BYTE ndata[] = { 0xe9,0x00,0x00,0x00,0x00,0xeb, 0xf9};
		adr-=5;  // go back to where the nops should be
		*(DWORD*)(&ndata[1]) =  (caveadr - adr) - 5;	    	 // put the correct offset in the repl string
		MemPatch((UCHAR*)adr, ndata,7);

		return (adr+7);
	}
	else{
		BYTE ndata[] = { 0xe9,0x00,0x00,0x00,0x00};
		BYTE dipdata[] = {0xeb, 0xd6};
		adr-=5;  // go back to where the nops should be
		*(DWORD*)(&ndata[1]) =  (caveadr - adr)-5;	    	 // put the correct offset in the repl string
		MemPatch((UCHAR*)adr, ndata, 5);
		long offset = 0x28; //0x4FDD8863(xor edi, edi) - adr;
		adr += offset;
		MemPatch((UCHAR*)adr, dipdata, 2);

		return (adr+2);
	}
}

//-----------------------//
// cTools::FindDevice
//-----------------------//
DWORD** cTools::FindDevice(VOID) // written by Croner
{
    DWORD Base = (DWORD)LoadLibraryA("d3d9.dll");

    for(DWORD i = 0; i < 0x128000; i++ )
    {
      if ( (*(BYTE *)(Base+i+0x00))==0xC7
        && (*(BYTE *)(Base+i+0x01))==0x06
        && (*(BYTE *)(Base+i+0x06))==0x89
        && (*(BYTE *)(Base+i+0x07))==0x86
        && (*(BYTE *)(Base+i+0x0C))==0x89
        && (*(BYTE *)(Base+i+0x0D))==0x86 )
        return (unsigned long**)(Base + i + 2);
    }
    return NULL;
}  


//-----------------------//
// cTools::bCompare
//-----------------------//
bool cTools::bCompare(PBYTE pData, PBYTE bMask, PCHAR szMask) //written by sb // funkcja do skanowania pamieci
{
	for(;*szMask;++szMask,++pData,++bMask)
		if(*szMask=='x' && *pData!=*bMask ) 
			return false;

	return (*szMask) == NULL;
}
//-----------------------//
// cTools::FindPattern
//-----------------------//
DWORD cTools::FindPattern(DWORD dwAddress,DWORD dwLen,PBYTE bMask,PCHAR szMask) //written by sb // funkcja do skanowania pamieci
{
	for(DWORD i=0; i < dwLen; i++)
		if( bCompare( (BYTE*)( dwAddress+i ), bMask, szMask) )
			return (DWORD)(dwAddress+i);

	return 0;
}
//-----------------------//
// cTools::XorStr
//-----------------------//
VOID cTools::XorStr(char* str, int key)
{
	int len = strlen(str);

	for(int i = 0; i < len; i++){
		str[i] ^= key;
	}
}
//-----------------------//
// cTools::GetFrameRate
//-----------------------//
char* WINAPI cTools::GetFrameRate()
{
	static float						 fFps            = NULL;
	static float                        fLastTickCount        = NULL;
	static float                        fCurrentTickCount;
	static char                        cFrameRate[50]        = {NULL};
	fCurrentTickCount = clock() * 0.001f;
	++fFps;
	if( (fCurrentTickCount - fLastTickCount) > 1.0f ){
		fLastTickCount = fCurrentTickCount;
		sprintf( cFrameRate, "%d", int( fFps ) );
		fFps = 0;
	}
	return cFrameRate;
}
//-----------------------//
// cTools::GetFrameRate
//-----------------------//
HRESULT cTools::GenerateTexture(IDirect3DDevice9 *pD3Ddev, IDirect3DTexture9 **ppD3Dtex, DWORD colour32)
{
	if( FAILED(pD3Ddev->CreateTexture(8, 8, 1, 0, D3DFMT_A4R4G4B4, D3DPOOL_MANAGED, ppD3Dtex, NULL)) )
		return E_FAIL;
 
	WORD colour16 = ( ( WORD ) ( ( colour32 >> 28 ) & 0xF ) << 12 )
	| (WORD)( ( ( colour32 >> 20 ) & 0xF ) << 8 )
	| (WORD)( ( ( colour32 >> 12 ) & 0xF ) << 4 )
	| (WORD)( ( ( colour32 >> 4 ) & 0xF ) << 0 );

	D3DLOCKED_RECT d3dlr; 
	(*ppD3Dtex)->LockRect(0, &d3dlr, 0, 0);
	WORD *pDst16 = (WORD*)d3dlr.pBits;
	for(int xy=0; xy < 8*8; xy++)
		*pDst16++ = colour16;
	(*ppD3Dtex)->UnlockRect(0);
	return S_OK;
}